<template>
<div class="room-page">
  <div class="left">
    <div class="left-header">
      <div class="meeting-id">会议号：{{ roomId }}</div>
      <div class="speaking-name">正在讲话：{{ speakingUserNames }}</div>
      <div v-if="getUserName(selected)" class="video-name">{{ getUserName(selected) }}</div>
    </div>
    <div class="left-top">
      <video ref='videoViewElemRef' autoPlay muted style="height: 100%;width:100%;padding: 0px;margin: 0px;background-color: #000000;opacity: 1;"/>
    </div>
    <div v-if="me"  class="left-bottom">
      <el-tooltip class="item" effect="dark" content="麦克风" placement="top">
        <div :class="getClassMic(me.audioProducer)?'button_mic_on':'button_mic_off'" @click="clickMic(me.audioProducer)" class="icon-style button button_mic_on"></div>
      </el-tooltip>
      <el-tooltip class="item" effect="dark" content="摄像头" placement="top">
        <div :class="getClassWebcam(me.videoProducer)?'button_webcam_on':'button_webcam_off'" @click="clickWebcam(me.videoProducer)" class="icon-style button button_webcam_on"></div>
      </el-tooltip>
      <el-tooltip class="item" effect="dark" content="屏幕共享" placement="top">
        <div :class="getClassShare(me.videoProducer)?'button_share_on':'button_share_off'" @click="clickShare(me.videoProducer)" class="icon-style button button_share_on"></div>
      </el-tooltip>
      <el-tooltip class="item" effect="dark" content="退出" placement="top">
        <div @click="$router.replace('/')" class="icon-style button icon-exit"></div>
      </el-tooltip>
    </div>
    <ChatInputBox ref="ChatInputBoxRef" v-if="me" @msg="msgSend"></ChatInputBox>
  </div>
  <div class="right" v-if="client">
    <el-radio-group v-model="selected" @input="selectedChange">
      <el-radio class="el-radio-button" :disabled="me.videoTrack==null" v-if="me" :label="-1">
        <peer-view style="border-radius: 5px;" v-if="me" :info="me" :isMe="true" :audioTrack="me.audioTrack" :videoTrack="me.videoTrack"
                  @muteMic="client.muteMic()"
                  @unmuteMic="client.unmuteMic()"
                  @disableWebcam="client.disableWebcam()"
                  @enableWebcam="client.enableWebcam()"
                  @disableShare="client.disableShare()"
                  @enableShare="client.enableShare()"
                  @audioVolume="(volume)=>(audioVolumeChange(-1,me.userName,volume))"
        ></peer-view>
        <div style="text-align: center;padding-bottom: 5px;color: #000000;">{{ me.userName }}</div>
      </el-radio>
      <div class="right-other">
        <el-radio :label="item.socketId" :disabled="item.videoTrack==null" v-for="(item,index) in others" :key="index" style="margin-top: 5px;">
          <peer-view style="border-radius: 5px;" :info="item" :audioTrack="item.audioTrack" :videoTrack="item.videoTrack"
                     @audioVolume="(volume)=>(audioVolumeChange(item.socketId,item.userName,volume))"></peer-view>
          <div style="text-align: center;padding-bottom: 5px;color: #000000;">{{ item.userName }}</div>
        </el-radio>
      </div>
    </el-radio-group>
  </div>
</div>
</template>

<script>
  import RoomClient from "./RoomClient";
  import PeerView from "../components/PeerView";
  import ChatInputBox from "../components/ChatInputBox";
  export default {
    name: "Room",
    components:{ PeerView,ChatInputBox },
    data(){
      return {
        roomId: null,// 会议id
        userName: null,// 用户名
        client: null,
        selected: null,// 选中的
        me:null,
        others:[],
        speakingUser: {},// 正在讲话
        speakingUserNames: '',// 正在讲话
      }
    },
    methods: {
      clickMic(audioProducer){
        if(this.getClassMic(audioProducer)){
          this.client.muteMic();
        }else{
          this.client.unmuteMic()
        }
      },
      clickWebcam(videoProducer){
        if(this.getClassWebcam(videoProducer)){
          this.client.disableWebcam()
        }else{
          this.client.enableWebcam()
        }
      },
      clickShare(videoProducer){
        if(this.getClassShare(videoProducer)){
          this.client.disableShare()
        }else{
          this.client.enableShare()
        }
      },
      selectedChange(index){
        try{
          console.log(index,this.selected)
          let videoTrack = null;
          if(index == -1){
            videoTrack = this.me.videoTrack?this.me.videoTrack:null;
          }else{
            let find = this.others.find(item=>item.socketId==index);
            videoTrack = find?find.videoTrack:null;
          }
          const { videoViewElemRef } = this.$refs;
          if (videoTrack) {
            const stream = new MediaStream;
            stream.addTrack(videoTrack);
            videoViewElemRef.srcObject = stream;
            videoViewElemRef.play().catch((error) => console.warn('videoViewElemRef.play() failed:%o', error));
          } else {
            videoViewElemRef.srcObject = null;
            this.selected = null;
          }
        }catch (e) {
        }
      },
      msgSend(msg){
        this.client.sendTextMessage(this.userName,msg);
      },
      audioVolumeChange(socketId,userName,volume){
        this.speakingUser[socketId] = {
          userName,
          volume
        }
        let resList = [];
        for(let key in this.speakingUser){
          const {userName,volume} = this.speakingUser[key];
          if(volume > 0){
            resList.push(userName);
          }
        }
        this.speakingUserNames = resList.join(';');
      }
    },
    computed:{
      producerChange(){
        if(this.client){
          const {_micProducer,_webcamProducer,_shareProducer,_device,_userName} = this.client;
          return { _micProducer,_webcamProducer,_shareProducer,_device,_userName }
        }
        return null;
      },
      consumerChange(){
        if(this.client){
          const {_consumers,_consumersLength} = this.client;
          return {
            _consumersLength,
            _consumers,
          };
        }
        return null;
      },
      getClassMic(){
        return (audioProducer)=>{
          if(audioProducer&&!audioProducer.paused){
            return true;
          }else{
            return false;
          }
        }
      },
      getClassWebcam(){
        return (videoProducer)=>{
          if(videoProducer&&!videoProducer.appData.share&&!videoProducer.paused){
            return true;
          }else{
            return false;
          }
        }
      },
      getClassShare(){
        return (videoProducer)=>{
          if(videoProducer&&videoProducer.appData.share&&!videoProducer.paused){
            return true;
          }else{
            return false;
          }
        }
      },
      getUserName(){
        return (selected)=>{
          try{
            if(selected){
              if(selected==-1){
                return this.me?this.me.userName+"的视频":'';
              }else{
                return this.others.find(item=>item.socketId==selected).userName+"的视频";
              }
            }else{
              return '';
            }
          }catch(e){
            return '';
          }
        }
      },
    },
    watch:{
      producerChange(newValue,oldValue){
        const { _micProducer,_webcamProducer,_shareProducer,_device,_userName }=newValue;
        if(_webcamProducer||_shareProducer){
          this.me={
            audioTrack: _micProducer?_micProducer.track:null,
            videoTrack: _webcamProducer?_webcamProducer.track:_shareProducer.track,
            audioProducer: _micProducer,
            videoProducer: _webcamProducer?_webcamProducer:_shareProducer,
            device:_device,
            userName:_userName
          };
        }else{
          this.me={
            audioTrack: _micProducer?_micProducer.track:null,
            videoTrack:null,
            audioProducer:_micProducer,
            videoProducer:null,
            device:_device,
            userName:_userName
          };
        }
        if(this.selected){
          this.selectedChange(this.selected);
        }else if(this.me.videoTrack){
          this.selected = -1;
          this.selectedChange(-1);
        }
      },
      consumerChange(newValue,oldValue){
        const { _consumersLength,_consumers }=newValue;
        if(_consumers.size>0){
          const res= {};
          _consumers.forEach(item=>{
            const {appData:{device,socketId,userName},kind,track}=item;
            if(res[socketId]){
              if(kind=='audio'){
                res[socketId].audioTrack=track;
                res[socketId].audioConsumer=item;
              }else{
                res[socketId].videoTrack=track;
                res[socketId].videoConsumer=item;
              }
            }else{
              res[socketId]={
                socketId,
                device,
                userName,
                audioTrack:kind=='audio'?track:null,
                videoTrack:kind=='video'?track:null,
                audioConsumer:kind=='audio'?item:null,
                videoConsumer:kind=='video'?item:null
              };
            }
          });
          let others=[];
          for(let key in res){
            others.push(res[key]);
          }
          this.others=others;
        }else{
          this.others=[];
        }
        if(this.selected){
          this.selectedChange(this.selected);
        }else{
          for(let i of this.others){
            if(i.videoTrack){
              this.selected = i.socketId;
              this.selectedChange(i.socketId);
              break;
            }
          }
        }
      }
    },
    created() {
      const {roomId,userName} = this.$route.query;
      if(!roomId||!userName){
        this.$router.push({
          path: '/',
          query: {
            roomId,
            userName
          }
        });
        return;
      }
      this.roomId = roomId;
      this.userName = userName;
      let client = new RoomClient({roomId,userName});
      client.on("error",(data)=>{
        this.$message.error(data);
      })
      client.on("close",(data)=>{
        console.log(data)
      })
      client.on("onMessage",(data)=>{
        console.log(data)
        this.$refs.ChatInputBoxRef.messageReceive(data);
      })
      client.on("open",()=>{
        this.clickMic(this.me.audioProducer);
        this.$message('默认为你禁音');
      })
      client.joinRoom();
      this.client=client;
    },
    destroyed() {
      this.client.close('页面销毁');
    }
  }
</script>

<style scoped>
.room-page{
  display: flex;
  height: 100vh;
  width: 100%;
  box-sizing: border-box;
  overflow: hidden;
}
.left{
  flex: 1;
  align-items: center;
  display: flex;
  flex-direction: column;
  position: relative;
}
.left-header{
  width: 100%;
  padding: 5px;
  box-sizing: border-box;
  display: flex;
  border-bottom: 1px dashed #ffffff;
}
.meeting-id{
  background-color: #056de8;
  padding: 5px 10px;
  margin-right: 10px;
  border-radius: 5px;
}
.speaking-name{
  width: 200px;
  overflow: hidden;
  margin-right: 10px;
  background-color: #e7f0fd;
  color: #0c70e8;
  padding: 5px 10px;
  border-radius: 5px;
}
.video-name{
  background-color: #ffffff;
  color: #000000;
  padding: 5px 10px;
  border-radius: 5px;
}
.left-top{
  flex: 1;
  padding: 10px;
  overflow: hidden;
}
.left-bottom{
  display: flex;
  width: 100%;
  padding: 10px;
  box-sizing: border-box;
  border-top: 1px dashed #ffffff;
  justify-content: end;
}
.icon-style{
  height: 50px;
  width: 50px;
  margin-right: 30px;
  border: 1px dashed #ffffff;
}
.right{
  height: 100%;
  padding: 5px;
  box-sizing: border-box;
  overflow: hidden;
  display: flex;
  flex-direction: column;
  border-left: 1px dashed #ffffff;
}
.right-other {
  flex: 1;
  display: flex;
  flex-direction: column;
  overflow: auto;
}
/deep/ .el-radio-group{
  height: 100%;
  display: flex;
  flex-direction: column;
}
/deep/ .el-radio.is-checked{
  background-color: #349ee6;
  color: #ffffff;
}
/deep/ .el-radio{
  margin: unset;
  background-color: #ffffff;
  border-radius: 5px;
  box-sizing: border-box;
}
/deep/ .el-radio__label{
  padding: unset;
}
/deep/ .el-radio__input{
  display: none;
}
.el-radio-button /deep/ .el-radio-button__inner{
  padding: unset;
  display: flex;
  flex-direction: column;
}
::v-deep .el-form--label-top .el-form-item__label{
  padding: unset;
}
::v-deep .el-form-item__label{
  line-height: unset;
}
::v-deep .el-popover{
  padding: 10px;
}
/*滚动条*/
::-webkit-scrollbar {
  width: 7px;/*右边的滚动条宽度*/
  height: 7px;/*下方的滚动条高度*/
  /*background-color: red;!*滚动条背景*!*/
}
/*滑块*/
::-webkit-scrollbar-thumb {
  border: 1px solid #fff;
  border-radius: 6px;
  background: #c9c9c9; /*滑块颜色*/
}
</style>
